import ctypes
import os, sys
# This is the folder containing the whole library.
sys.path.append(
    os.path.abspath(
        os.path.join(
            os.path.dirname(__file__), "../../")))
from lib3ddevil1.bindings import libc
del os, sys

#--------------------------------------+
#       Basic Struct
#--------------------------------------+

class PldHeader(ctypes.Structure):
    _pack_   = 1
    _fields_ = [
        ("numOffset", ctypes.c_int),
        ("offsets",   ctypes.POINTER(ctypes.c_int))
    ]

class Devil1PLD_FN(ctypes.Structure):
    _fields_ = [
        ("getheader"   , ctypes.CFUNCTYPE(
                                          ctypes.c_bool,
                                          ctypes.POINTER(PldHeader),
                                          ctypes.c_char_p)),
        ("sizeofsector", ctypes.CFUNCTYPE(
                                          ctypes.c_int,  
                                          ctypes.POINTER(PldHeader), 
                                          ctypes.c_int)),
        ("printheader" , ctypes.CFUNCTYPE(None, 
                                          ctypes.POINTER(PldHeader)))
    ]

devil1pld = Devil1PLD_FN.in_dll(libc, "DEVIL1PLD")
del libc

#--------------------------------------+
#       Pythonic Object
#--------------------------------------+

class pyPldHeader:
    def __init__(self, filedata = None):
        # Store C Struct in order to call C functions
        self.cstruct = PldHeader()
        if filedata:
            if not devil1pld.getheader(ctypes.byref(self.cstruct), filedata):
                raise RuntimeError("failed to get .pld header")
            self.eof = len(filedata)

    def show(self):
        devil1pld.printheader(ctypes.byref(self.cstruct))
        return

    def getnumoffsets(self):
        return self.cstruct.numOffsets

    # return pythonic list of offsets
    def getoffsets(self):
        return self.cstruct.offsets[:self.cstruct.numOffset]

    def sizeofsector(self, i):
        ptr = ctypes.byref(self.cstruct)
        return devil1pld.sizeofsector(ptr, i, self.eof)

